import java.util.LinkedList;

/**
 * 描述：使用链表来进行队列的模拟
 *
 * @author WangB
 * @create 2018-10-20-0:26
 */
public class LinkedListQueue<E> implements Queue<E>{
    private class Node{
        public E e;
        public Node next;

        /**
         * 这个构造函数是传入e和next
         * @param e
         * @param next
         */
        public Node(E e,Node next){
            this.e = e ;
            this.next = next;
        }

        /**
         * 这个构造函数只传入e
         * @param e
         */
        public Node(E e){
            this(e,null);
        }

        /**
         * 这个构造函数什么也不传入
         */
        public Node(){
            this(null,null);
        }

        @Override
        public String toString(){
            return e.toString();
        }
    };

    private Node head,tail;
    private int size ;

    public LinkedListQueue(){
        head = null;
        tail = null;
        size = 0 ;
    }

    @Override
    public int getSize(){
        return size;
    }

    @Override
    public boolean isEmpty(){
        return size == 0 ;
    }

    @Override
    public void enqueue(E e){
        if(tail == null){
            //如果tail是空的情况下，那么head也一定是空的。
            tail = new Node ( e );
            head = tail;
        }else{
            tail.next = new Node ( e );
            tail = tail.next;
        }
        size++;
    }

    @Override
    public E dequeue(){
        if(isEmpty ())
            throw new IllegalArgumentException ( "队列啥都没有，没法出队" );
        Node retNode = head;
        head = head.next;
        retNode.next = null;
        if(head == null) //如果队列只有一个元素的时候，我移除了之后就变成了空的了，因此需要维护一下tail
            tail = null;
        size--;
        return retNode.e;
    }

    @Override
    public E getFront(){
        if(isEmpty ())
            throw new IllegalArgumentException ( "队列啥都没有，没法出队" );
        return head.e;
    }

    @Override
    public String toString(){
        StringBuilder res= new  StringBuilder();
        res.append ( "Queue front " );
        Node cur = head;

        while(cur != null){
            res.append ( cur + "->" );
            cur = cur.next;
        }
        res.append("NULL tail");
        return res.toString ();
    }
    public static void main(String[] args)
    {
        LinkedListQueue<Integer> queue = new LinkedListQueue<>();
        for (int i = 0; i < 20; i++) {
            queue.enqueue(i);
            System.out.println(queue);

            if(i % 3 == 2){

                queue.dequeue();
                System.out.println(queue);
            }

        }


    }
}
